package service

import (
	"encoding/json"
	log "github.com/sirupsen/logrus"
	"os/exec"
	"strings"
	"usbipproxy/domain/vo"
)

type UsbIpServerLinuxCmdServiceImpl struct{}

func (u *UsbIpServerLinuxCmdServiceImpl) UnBind(busId string) (bool, error) {
	cmds := []string{"usbip", "unbind", "-b", busId}
	log.Infof("UsbIpServerLinuxCmdServiceImpl UnBind cmds:%+v", cmds)
	str, err := exec.Command(cmds[0], cmds[1:]...).CombinedOutput()
	if err != nil {
		log.Errorf("UsbIpServerLinuxCmdServiceImpl err:%v str:%v", err, string(str))
		return false, err
	}
	log.Infof("UsbIpServerLinuxCmdServiceImpl ret:%v", string(str))
	return true, nil
}

func (u *UsbIpServerLinuxCmdServiceImpl) Bind(busId string) (bool, error) {
	cmds := []string{"usbip", "bind", "-b", busId}
	log.Infof("UsbIpServerLinuxCmdServiceImpl Bind cmds:%+v", cmds)
	str, err := exec.Command(cmds[0], cmds[1:]...).CombinedOutput()
	if err != nil {
		log.Errorf("UsbIpAttachList err:%v str:%v", err, string(str))
		return false, err
	}
	log.Infof("UsbIpAttachList ret:%v", string(str))
	if !strings.Contains(string(str), "complete") {
		return false, nil
	}
	return true, err
}

func (u *UsbIpServerLinuxCmdServiceImpl) List() []*vo.UsbInfo {
	str, err := exec.Command("usbip", "list", "-l").CombinedOutput()
	if err != nil {
		log.Errorf("UsbIpList err:%v", err)
		return nil
	}

	strs := strings.Split(string(str), "\n")

	var result []*vo.UsbInfo
	begin := false
	var usbInfo *vo.UsbInfo
	for _, line := range strs {
		log.Infof("UsbIpServerLinuxCmdServiceImpl List: %v", line)
		if !begin {
			//- busid 3-1 (0e0f:0003)
			if strings.Contains(line, "busid") {
				usbInfo = &vo.UsbInfo{}
				begin = true
				fileds := strings.Fields(line)
				if len(fileds) == 4 {
					usbInfo.BusId = fileds[2]
					usbInfo.VendorId = fileds[3]
					usbInfo.VendorId = strings.TrimPrefix(usbInfo.VendorId, "(")
					usbInfo.VendorId = strings.TrimRight(usbInfo.VendorId, ")")
				}
				//log.Infof("fileds: %v len(fileds):%v", fileds, len(fileds))
			}
		} else {
			//log.Infof("2222")
			//VMware, Inc. : Virtual Mouse (0e0f:0003)
			parts := parseDeviceInfo(line)
			usbInfo.Vendor = parts[0]
			usbInfo.Product = parts[1]

			result = append(result, usbInfo)
			begin = false
		}
	}

	resultByte, _ := json.Marshal(result)
	log.Infof("UsbIpServerLinuxCmdServiceImpl List: %+v", string(resultByte))
	return result
}

func NewUsbIpServerLinuxCmdServiceImpl() UsbIpServerCmdService {
	return &UsbIpServerLinuxCmdServiceImpl{}
}

func parseDeviceInfo(input string) []string {
	// 1. 按冒号分割成两部分
	parts := strings.SplitN(input, ":", 2)

	// 2. 处理左侧部分 - 去除首尾空格
	left := strings.TrimSpace(parts[0])

	// 3. 处理右侧部分
	right := ""
	if len(parts) > 1 {
		// 去除首尾空格
		right = strings.TrimSpace(parts[1])

		// 截取到第一个左括号前的部分
		if idx := strings.Index(right, " ("); idx != -1 {
			right = right[:idx]
		}
	}

	// 4. 返回格式为 []string{"左侧", "右侧"}
	return []string{left, right}
}
